package services

import (
	"context"
	"encoding/json"
	"fmt"
	client2 "github.com/micro/go-micro/v2/client"
	uuid "github.com/satori/go.uuid"
	"log"
	"micro-member/datamodels"
	"micro-member/initialize"
	"micro-member/libs"
	"micro-member/proto/user"
	"micro-member/repositories"
	"strconv"
	"time"
)

type UserInterfaceService interface {
	Test(ctx context.Context, in *user.TestRequest, out *user.TestResponse) error
	Register(ctx context.Context, in *user.RegisterRequest, out *user.RegisterResponse) error
	GetUserInfo(ctx context.Context, in *user.GetUserByIdRequest, out *user.GetUserByIdResponse) error
	UserLogin(ctx context.Context, in *user.UserLoginRequest, out *user.UserLoginResponse) error
	UpdateUser(ctx context.Context, in *user.UpdateUserRequest, out *user.UpdateUserResponse) error
}

//初始化对象函数
func NewUserService(name string,c client2.Client) UserInterfaceService {
	return &UserService{
		client:c,
		name:name,
		bbsPostService:          repositories.NewBbsPost(),
		userService:             repositories.NewUserRepoInterface(),
	}
}

type UserService struct {
	client client2.Client
	name string
	bbsPostService 			repositories.BbsPostInterface       //社区帖子服务
	userService 			repositories.UserRepoInterface      //用户服务
}

func(this *UserService) Test(ctx context.Context, req *user.TestRequest, rsp *user.TestResponse) error {
	rsp.Success = "users" + req.Id
	//服务之间调用 todo
	//c := course.NewCourseService("go.micro.api.course",this.client)
	//course_rsp,_ := c.ListForTop(ctx,&course.ListRequest{Size:10})
	//log.Println("course_rsp获取结果：",course_rsp.Result)
	return nil
}

//用户注册
func(this *UserService) Register(ctx context.Context, in *user.RegisterRequest, out *user.RegisterResponse) error{
	fmt.Println("进入Register方法")
	var user datamodels.User
	user.Nickname = in.Nickname
	user.Email = in.Email
	user.Reward = 20
	user.Uid = uuid.NewV4().String()
	user.CreateTime = time.Now().Unix()
	user.Password = libs.GenSaltPassword(in.Password, strconv.FormatInt(user.CreateTime,10))//已用户注册时间为盐值
	user.HeadImg = "https://bbs.100txy.com/public/static/res/images/avatar/default.png"
	fmt.Println("user:",user)

	_, err := this.userService.Insert(user)
	if err !=nil {
		return  err
	}
	out.Success = true
	return nil
}

//获取用户信息
func(this *UserService) GetUserInfo(ctx context.Context, req *user.GetUserByIdRequest, rsp *user.GetUserByIdResponse) error{
	fmt.Println("GetUserByIdRequest:",req)
	var userInfo user.User
	redisUserInfo := initialize.RedisClient.Get("member:userinfo:"+strconv.FormatInt(req.UserId,10))
	if redisUserInfo.Val() != ""{
		var redisUser user.User
		json.Unmarshal([]byte(redisUserInfo.Val()), &redisUser)
		//userInfo.Id = req.UserId
		//userInfo.Nickname = redisUser.Nickname
		//userInfo.HeadImg = redisUser.HeadImg
		//userInfo.IsAdmin = redisUser.IsAdmin
		//userInfo.IsVip = redisUser.IsVip
		//userInfo.Status = redisUser.Status
		//userInfo.Reward = redisUser.Reward
		fmt.Println("返回缓存数据")
		rsp.Result = &redisUser
		return nil
	}
	dbUserInfo, err := this.userService.SelectInfo(req.UserId)
	if err != nil {
		log.Println("[用户服务——查找用户信息失败]-[%s]", err.Error())
		return nil
	}
	redisDbUserInfo, _ := json.Marshal(dbUserInfo)
	initialize.RedisClient.Set("member:userinfo:"+strconv.FormatInt(req.UserId,10),redisDbUserInfo,-1)
	userInfo.Id = req.UserId
	userInfo.Uid = dbUserInfo.Uid
	userInfo.Type = dbUserInfo.Type
	userInfo.Nickname = dbUserInfo.Nickname
	userInfo.HeadImg = dbUserInfo.HeadImg
	userInfo.IsAdmin = dbUserInfo.IsAdmin
	userInfo.IsVip = dbUserInfo.IsVip
	userInfo.Password = dbUserInfo.Password
	userInfo.Phone = dbUserInfo.Phone
	userInfo.Status = dbUserInfo.Status
	userInfo.Reward = dbUserInfo.Reward
	rsp.Result = &userInfo
	fmt.Println("返回数据库数据")
	return nil
}

//检验用户登录
func(this *UserService) UserLogin(ctx context.Context, req *user.UserLoginRequest, rsp *user.UserLoginResponse) error{
	fmt.Println("进入UserLogin方法")
	fmt.Println("UserLoginRequest:",req)
	userinfo, err := this.userService.CheckUserLoginInfo(req.Nickname, req.Password)
	if err != nil {
		rsp.User = nil
		rsp.Res = false
		return nil
	}
	var user user.User
	user.Id = userinfo.ID
	user.Nickname = userinfo.Nickname
	user.HeadImg = userinfo.HeadImg
	user.Phone = userinfo.Phone
	rsp.User = &user
	rsp.Res = true
	return nil
}

//更新用户信息
func(this *UserService) UpdateUser(ctx context.Context, req *user.UpdateUserRequest, rsp *user.UpdateUserResponse) error{
	fmt.Println("req.User:",req.User)
	val := make(map[string]interface{})
	if req.User.Nickname != ""{
		val["nickname"] = req.User.Nickname
	}
	if req.User.HeadImg != ""{
		val["head_img"] = req.User.HeadImg
	}
	if req.User.IsAdmin != 0{
		val["is_admin"] = req.User.IsAdmin
	}
	if req.User.IsVip != 0{
		val["is_vip"] = req.User.IsVip
	}
	if req.User.Phone != ""{
		val["phone"] = req.User.Phone
	}
	if req.User.Password != ""{
		val["password"] = req.User.Password
	}
	if req.User.Status != 0{
		val["status"] = req.User.Status
	}
	if req.User.Reward != 0{
		val["reward"] = req.User.Reward
	}
	val["update_time"] = time.Now().Unix()
	//更新用户信息
	where := map[string]interface{}{
		"id": req.User.Id,
	}
	var num int64
	var typo string
	var remark string
	switch req.Typo {
		case "publish":
			typo = "PUBLISH"
			num = -req.Number
			remark = "发布帖子消费飞吻"
		case "signin":
			typo = "SIGNIN"
			num = req.Number
			remark = "签到奖励飞吻"
		default:
			typo = "PUBLISH"
			num = -req.Number
			remark = "发布帖子消费飞吻"
	}
	id, err := this.userService.UpdateUserInfo(where,val,num,typo,remark)
	if err != nil {
		rsp.RecordId = 0
		return nil
	}
	//更新缓存
	initialize.RedisClient.Del("member:userinfo:"+strconv.FormatInt(req.User.Id,10)).Result()
	rsp.RecordId = id
	return nil
}